package com.ece.pfe_rover_pvt_ines_ece_application.view;

import java.sql.Ref;
import java.text.SimpleDateFormat;
import java.util.Arrays;
import java.util.Calendar;
import java.util.Date;
import java.util.GregorianCalendar;
import java.util.List;

import com.ece.pfe_rover_pvt_ines_ece_application.PFE_ROVER_PVT_INES_ECE_Application;
import com.ece.pfe_rover_pvt_ines_ece_application.R;
import com.ece.pfe_rover_pvt_ines_ece_application.model.Measurements;
import com.parse.ParseAnonymousUtils;
import com.parse.ParseException;
import com.parse.ParseObject;
import com.parse.ParseQuery;
import com.parse.ParseUser;
import com.parse.ui.ParseLoginBuilder;

import android.app.ActionBar.LayoutParams;
import android.app.ActionBar;
import android.app.Activity;
import android.app.DatePickerDialog;
import android.app.Dialog;
import android.app.TimePickerDialog;
import android.content.Intent;
import android.content.res.Resources;
import android.graphics.Color;
import android.graphics.Typeface;
import android.os.Bundle;
import android.util.Log;
import android.view.Gravity;
import android.view.LayoutInflater;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.CheckBox;
import android.widget.DatePicker;
import android.widget.HorizontalScrollView;
import android.widget.RelativeLayout;
import android.widget.ScrollView;
import android.widget.TableLayout;
import android.widget.TableRow;
import android.widget.TextView;
import android.widget.TimePicker;
import android.widget.Toast;

public class TableActivity extends Activity {
	public boolean DEBUG_MODE = PFE_ROVER_PVT_INES_ECE_Application.DEBUG;

	private static final int LOGIN_ACTIVITY_CODE = 100;
	public static final int TIME_DIALOG_ID_DEBUT = 1;
	public static final int DATE_DIALOG_ID_DEBUT = 2;
	public static final int TIME_DIALOG_ID_FIN = 3;
	public static final int DATE_DIALOG_ID_FIN = 4;

	private Button btnSelectDate, btnSelectTime, btnSelectDate2, btnSelectTime2, effacer, afficher;
	private CheckBox pv1, pv2, paramDefault;
	
	
	// variables returned by the dialog (start & end)
	private int year, month, day, hour, minute;
	private int endYear, endMonth, endDay;
	private int mYear, mMonth, mDay, mHour, mMinute, fYear, fMonth, fDay,
			fHour, fMinute;
	private Calendar startDate, endDate;
		
	private List<Measurements> result = null;
	private final SimpleDateFormat sdf = new SimpleDateFormat("dd/MM/yyyy HH:mm");
	
	private TableLayout tableLayout;
	private RelativeLayout root;
	private RelativeLayout.LayoutParams params;
	private ScrollView sv;
	private HorizontalScrollView hsv;
	
	private int cl, rl; // column & row length
	private String[] row;
	String[] column = { "EntryId\n", "ID PV\n(1,2)", "I \n(A)", "V\n(V)", "PUISSANCE\n(W)", "LUMINOSITE\n(W/m2)",
			"T PV\n(°C)", "T EXT\n(°C)", "GPS\n", "VITESSE VENT\n(m/s)", "TIMESTAMP\n" };
	
	// Checkboxes values
	private boolean cbpv1 = true,cbpv2 = true, cbparamDefault = false;
	
	

	@Override
	protected void onCreate(Bundle savedInstanceState) {															
		//Activity that links menu button to the table layout
		super.onCreate(savedInstanceState);
		setContentView(R.layout.activity_table);				
		
		//Menu & subtitle
		ActionBar actionBar = getActionBar();		
		actionBar.setSubtitle(R.string.subtitle_table1);
		
		final SimpleDateFormat sdf = new SimpleDateFormat("dd/MM/yyyy HH:mm");
		
		startDate = new GregorianCalendar();				
		startDate.set(Calendar.YEAR, mYear);
		startDate.set(Calendar.MONTH, mMonth);
		startDate.set(Calendar.DAY_OF_MONTH, mDay);
		startDate.set(Calendar.HOUR, mDay);
		startDate.set(Calendar.MINUTE, mMinute);
		
		endDate = new GregorianCalendar();	
		endDate.set(Calendar.YEAR, mYear);
		endDate.set(Calendar.MONTH, mMonth);
		endDate.set(Calendar.DAY_OF_MONTH, mDay);
		endDate.set(Calendar.HOUR, mDay);
		endDate.set(Calendar.MINUTE, mMinute);
		
				
		//Rows and Colums of the table		
		LayoutInflater mInflater = LayoutInflater.from(this);
		View contentView = mInflater.inflate(R.layout.activity_table, null);
		root = (RelativeLayout) contentView;

		// Generate a query and retrieve the result as a list
		populateTableQuery();

		//Create the table
		int tableSize = result.size();
		System.out.println(result.size());
		
		String[] row = new String[tableSize];
		
		
		rl = row.length;
		cl = column.length;
		sv = new ScrollView(this);
		sv.setScrollbarFadingEnabled(false);
		
		tableLayout = createTableLayout(row, column, rl, cl);
		params = new RelativeLayout.LayoutParams(
				LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT);
		params.leftMargin = 400;		

		hsv = new HorizontalScrollView(this);
		hsv.setScrollbarFadingEnabled(false);
		hsv.addView(tableLayout);
		sv.addView(hsv);
		root.addView(sv, params);
		setContentView(root);

		// get the references of buttons
		btnSelectDate = (Button) findViewById(R.id.button_set_date1);
		btnSelectTime = (Button) findViewById(R.id.buttonSelectTime);
		btnSelectDate2 = (Button) findViewById(R.id.button_set_date2);
		btnSelectTime2 = (Button) findViewById(R.id.buttonSelectTime2);
		
		initializeDatePicker();
		
		afficher = (Button) findViewById(R.id.afficher);
		afficher.setOnClickListener(new OnClickListener() {
			@Override
			public void onClick(View v) {		
				Intent intent = new Intent(getBaseContext(), TableActivity2.class);
				
				
				System.out.println(sdf.format(startDate.getTimeInMillis()));
				System.out.println(sdf.format(endDate.getTimeInMillis()));
				
				intent.putExtra("startDate", startDate.getTimeInMillis()); 
				intent.putExtra("endDate", endDate.getTimeInMillis()); 
				intent.putExtra("PV1", cbpv1);
				intent.putExtra("PV2", cbpv2);
				intent.putExtra("paramDefault", cbparamDefault);
				intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_NEW_TASK);
				startActivity(intent);				
			}
		});
		
		// Set ClickListener on btnSelectDate
		btnSelectDate.setOnClickListener(new View.OnClickListener() {

			@SuppressWarnings("deprecation")
			public void onClick(View v) {
				// Show the DatePickerDialog
				showDialog(DATE_DIALOG_ID_DEBUT);
			}
		});

		// Set ClickListener on btnSelectTime
		btnSelectTime.setOnClickListener(new View.OnClickListener() {

			@SuppressWarnings("deprecation")
			public void onClick(View v) {
				// Show the TimePickerDialog
				showDialog(TIME_DIALOG_ID_DEBUT);
			}
		});

		// Set ClickListener on btnSelectDate
		btnSelectDate2.setOnClickListener(new View.OnClickListener() {

			@SuppressWarnings("deprecation")
			public void onClick(View v) {
				// Show the DatePickerDialog
				showDialog(DATE_DIALOG_ID_FIN);
			}
		});

		// Set ClickListener on btnSelectTime
		btnSelectTime2.setOnClickListener(new View.OnClickListener() {

			@SuppressWarnings("deprecation")
			public void onClick(View v) {
				// Show the TimePickerDialog
				showDialog(TIME_DIALOG_ID_FIN);
			}
		});
		
		int id = Resources.getSystem().getIdentifier("btn_check_holo_light", "drawable", "android");		
		((CheckBox) findViewById(R.id.pv1)).setButtonDrawable(id);
		((CheckBox) findViewById(R.id.pv2)).setButtonDrawable(id);	
		
		((TextView) findViewById(R.id.nbEntry)).append(" "+result.size());
		
		
		Toast toast = new Toast(getBaseContext());
		if(result.size() == 0) {
			toast = Toast.makeText(getBaseContext(), "Aucune mesure existante\n"
					+ " Synchronisez les données après avoir insérer la carte SD", Toast.LENGTH_LONG);
			toast.setGravity(Gravity.CENTER, 0, 0);
			toast.show();
		}
		
	}

	/**
	 * Initialize the date picker with current date
	 */
	private void initializeDatePicker() {
		year = 2015;
		month = Calendar.getInstance().get(Calendar.MONTH);
		day = Calendar.getInstance().getMinimum(Calendar.DAY_OF_MONTH);		
		startDate.set(year, month, day);				
		// Set the Selected Date in Select date Button
		btnSelectDate.setText("Date selected : " + day + "-" + (month+=1) + "-"
				+ year);	
		
		endYear = year;
		endMonth = month;
		endDay = Calendar.getInstance().getMaximum(Calendar.DAY_OF_MONTH);	
		endDate.set(endYear, endMonth, endDay);
		// Set the Selected Date in Select date Button
		btnSelectDate2.setText("Date selected : " + endDay + "-" + endMonth + "-"
				+ endYear);						
	}

	/**
	 * Query the local datastore
	 * Return all the measurements present in the file 
	 */
	private void populateTableQuery() {
		ParseQuery<Measurements> query = ParseQuery.getQuery(Measurements.class);
		query.fromLocalDatastore();
		query.selectKeys(Arrays.asList("EntryId","IdPan", "I", "V", "P", "Lum", "Tpan",
				"Tair", "GPS", "Swind", "Date"));
		query.orderByDescending("EntryId");
				
		try {
			result = query.find();
		} catch (ParseException e) {
			if(DEBUG_MODE) System.out.println("Query has not found anything");
			e.printStackTrace();
		}						
	}

	/**
	 * Listener for checkboxes
	 * When PV1 is checked, the result list is updated with panel 1 information
	 * Idem for PV2
	 * @param view
	 */
	public void onCheckboxClicked(View view) {
	    // Is the view now checked?
	    boolean checked = ((CheckBox) view).isChecked();
	    
	    ParseQuery<Measurements> query = ParseQuery.getQuery(Measurements.class);
	    query.fromLocalDatastore();
		query.selectKeys(Arrays.asList("EntryId","IdPan", "I", "V", "P", "Lum", "Tpan",
				"Tair", "GPS", "Swind", "Date"));			
		
	    // Check which checkbox was clicked
	    switch(view.getId()) {
	        case R.id.pv1:
	            if (checked)	            	
	            	cbpv1 = true;
	            else
	            	cbpv1 = false;
	            	query.whereEqualTo("IdPan", 1);
	            	System.out.println("PV1 clicked !");
	            break;
	        case R.id.pv2:
	        	if (checked)     
	        		cbpv2 = true;
	        	else
	        		cbpv2 = false;
	            	query.whereEqualTo("IdPan", "2");	
	            	System.out.println("PV2 clicked !");           
	            break; 	        
	    }
	    
	    query.orderByDescending("EntryId");
	    try {
			result = query.find();
		} catch (ParseException e) {
			if(DEBUG_MODE) System.out.println("Query has not found anything");
			e.printStackTrace();
		}	
	}
	
	/**
	 * Create the table layout that contains all our measurements
	 * @param rv : row values
	 * @param cv : column values
	 * @param rowCount
	 * @param columnCount
	 * @return
	 */
	private TableLayout createTableLayout(String[] rv, String[] cv,
			int rowCount, int columnCount) {
		// 1) Create a tableLayout and its params
		TableLayout.LayoutParams tableLayoutParams = new TableLayout.LayoutParams();
		TableLayout tableLayout = new TableLayout(this);
		tableLayout.setBackgroundColor(Color.BLACK);
		tableLayoutParams.height = 500;

		// 2) create tableRow params
		TableRow.LayoutParams tableRowParams = new TableRow.LayoutParams();
		tableRowParams.setMargins(1, 1, 1, 1);
		tableRowParams.weight = 1;
		
		
		for (int i = -1; i < rowCount; i++) {
			// 3) create tableRow
			TableRow tableRow = new TableRow(this);
			tableRow.setBackgroundColor(Color.BLACK);			
						
			for (int j = 0; j < columnCount; j++) {
				// 4) create textView
				TextView textView = new TextView(this);				
				textView.setBackgroundColor(Color.WHITE);
				textView.setGravity(Gravity.CENTER);
				textView.setPadding(2, 0 , 2, 0);
					
				if (i == -1) {				
					textView.setText(cv[j]);
					textView.setTextColor(Color.parseColor("maroon"));					
					textView.setTypeface(null, Typeface.BOLD);
				} else {					
					textView.setText(toTabString(result.get(i))[j]);
					textView.setTextColor(Color.BLACK);
				}
				// 5) add textView to tableRow
				tableRow.addView(textView, tableRowParams);
			}
			// 6) add tableRow to tableLayout
			tableLayout.addView(tableRow, tableLayoutParams);
		}

		return tableLayout;
	}

	/**
	 *  Register DatePickerDialog listener
	 */
	private DatePickerDialog.OnDateSetListener mDateSetListener = new DatePickerDialog.OnDateSetListener() {
		// the callback received when the user "sets" the Date in the
		// DatePickerDialog
		public void onDateSet(DatePicker view, int yearSelected,
				int monthOfYear, int dayOfMonth) {
			year = yearSelected;
			month = monthOfYear;
			day = dayOfMonth;
			
			startDate.set(year, month, day);			
	
			// Set the Selected Date in Select date Button
			btnSelectDate.setText("Date selected : " + day + "-" + (month+=1) + "-"
					+ year);		
		}	
	};
	
	
	private DatePickerDialog.OnDateSetListener fDateSetListener = new DatePickerDialog.OnDateSetListener() {
		// the callback received when the user "sets" the Date in the
		// DatePickerDialog
		public void onDateSet(DatePicker view, int yearSelectedfin,
				int monthOfYearfin, int dayOfMonthfin) {
			endYear = yearSelectedfin;
			endMonth = monthOfYearfin;
			endDay = dayOfMonthfin;
			
			endDate.set(endYear, endMonth, endDay);
			
			// Set the Selected Date in Select date Button
			btnSelectDate2.setText("Date selected : " + endDay + "-" + (endMonth+=1) + "-"
					+ endYear);
			System.out.println(endMonth);
		}
	};
	
	// Register TimePickerDialog listener
	private TimePickerDialog.OnTimeSetListener mTimeSetListener = new TimePickerDialog.OnTimeSetListener() {
		// the callback received when the user "sets" the TimePickerDialog in
		// the dialog
		public void onTimeSet(TimePicker view, int hourOfDay, int min) {
			hour = hourOfDay;
			minute = min;
			
			startDate.set(Calendar.HOUR_OF_DAY, hour);
			startDate.set(Calendar.MINUTE, minute);
			
			// Set the Selected Date in Select date Button
			btnSelectTime.setText("Time selected :" + hour + "-" + minute);
		}
	};
	
	private TimePickerDialog.OnTimeSetListener fTimeSetListener = new TimePickerDialog.OnTimeSetListener() {
		// the callback received when the user "sets" the TimePickerDialog in
		// the dialog
		public void onTimeSet(TimePicker view, int hourOfDayfin, int minfin) {
			hour = hourOfDayfin;
			minute = minfin;
			
			endDate.set(Calendar.HOUR_OF_DAY, hour);
			endDate.set(Calendar.MINUTE, minute);
			
			// Set the Selected Date in Select date Button
			btnSelectTime2.setText("Time selected :" + hour + "-" + minute);
		}
	};

	// Method automatically gets Called when you call showDialog() method
	@Override
	protected Dialog onCreateDialog(int id) {
		switch (id) {
		case DATE_DIALOG_ID_DEBUT:
			// create a new DatePickerDialog with values you want to show
			DatePickerDialog dpDialog = new DatePickerDialog(this, mDateSetListener, mYear, mMonth,
					mDay);
			DatePicker datePicker = dpDialog.getDatePicker();
			Calendar calendar = Calendar.getInstance();
			Date min = new Date(2015-1900, 0, 1);
			datePicker.setMinDate(min.getTime());
			return dpDialog;

		case DATE_DIALOG_ID_FIN:		
			DatePickerDialog dfDialog = new DatePickerDialog(this, fDateSetListener, fYear, fMonth,
					fDay);
			DatePicker datePicker2 = dfDialog.getDatePicker();
			Calendar calendar2 = Calendar.getInstance();
			Date min2 = new Date(2015-1900, 0, 1);
			datePicker2.setMinDate(min2.getTime());
			return dfDialog;
			
			// create a new TimePickerDialog with values you want to show
		case TIME_DIALOG_ID_DEBUT:
			return new TimePickerDialog(this, mTimeSetListener, mHour, mMinute,
					false);
		case TIME_DIALOG_ID_FIN:
			return new TimePickerDialog(this, fTimeSetListener, fHour, fMinute,
					false);
		}
		return null;
	}
	
	/**
	 * Convert a measurement to a String table
	 * @param m
	 * @return
	 */
	private String[] toTabString(Measurements m) {
		String[]tab = new String[cl];
		SimpleDateFormat sdf = new SimpleDateFormat("dd/MM/yyyy HH:mm");				
		GregorianCalendar date = new GregorianCalendar();
		date.setTimeInMillis(m.getDate());		
		
		tab[0] = String.valueOf(m.getEntryId());		
		tab[1] = String.valueOf(m.getInputId());
		tab[2] = String.valueOf(m.getI());
		tab[3] = String.valueOf(m.getV());
		tab[4] = String.valueOf(m.getP());
		tab[5] = String.valueOf(m.getLum());
		tab[6] = String.valueOf(m.getTpan());
		tab[7] = String.valueOf(m.getTair());
		tab[8] = String.valueOf(m.getGPS());
		tab[9] = String.valueOf(m.getSwind());
		tab[10] = String.valueOf(sdf.format(date.getTime()));
				
		return tab;
		
	}
	
	/**
	 * OnCreateOptionsMenu (Android method related to Activity class)
	 * Inflate the menu
	 */
	@Override
	public boolean onCreateOptionsMenu(Menu menu) {		
		// Inflate the menu
		//this adds items to the action bar if it is present.		
		getMenuInflater().inflate(R.menu.action_logout, menu);
		getMenuInflater().inflate(R.menu.activity_main_actions, menu);		
		getMenuInflater().inflate(R.menu.action_login, menu);							
		
		return true;
	}

	/**
	 * onOptionsItemSelected (Android method related to Activity class)
	 * Start the activity related to a selected field in the menu
	 */
	@Override
	public boolean onOptionsItemSelected(MenuItem item) {		
		// Handle action bar item clicks here. The action bar will
		// automatically handle clicks on the Home/Up button, so long
		// as you specify a parent activity in AndroidManifest.xml.
		int id = item.getItemId();
		switch(id) {
		
		case R.id.measurements_list:
			startActivity(new Intent(this.getBaseContext(),MeasureActivity.class));			
			return true;
		case R.id.measurements_graphs:
			startActivity(new Intent(this.getBaseContext(),GraphsActivity.class));			
			return true;
		
		case R.id.referentiel:
			startActivity(new Intent(this.getBaseContext(),ReferentielActivity.class));			
			return true;
			
		case R.id.action_logout:			
			// Log out the current user
			ParseUser.logOut();
			// Create a new anonymous user
			ParseAnonymousUtils.logIn(null);
						
			// Unpin all the current objects
			ParseObject
					.unpinAllInBackground(PFE_ROVER_PVT_INES_ECE_Application.MEASUREMENTS_GROUP_NAME);
			
			//End the activity & go back the the previous one
			finish();
			
			return super.onOptionsItemSelected(item);
			
		case R.id.action_login:
			invalidateOptionsMenu();
			ParseLoginBuilder builder = new ParseLoginBuilder(this);
			startActivityForResult(builder.build(), LOGIN_ACTIVITY_CODE);
			
			return super.onOptionsItemSelected(item);
		
		default:			
				return super.onOptionsItemSelected(item);
		}
	}
	
	/**
	 * onPrepareOptionsMenu
	 */
	@Override
	public boolean onPrepareOptionsMenu(Menu menu) {		
		
		if(DEBUG_MODE) System.out.println("---- Entering onPrepareOptopnsMenu method...");
		
		boolean realUser;
		super.onPrepareOptionsMenu(menu);
		if(ParseUser.getCurrentUser() != null){
			realUser = !ParseAnonymousUtils.isLinked(ParseUser
				.getCurrentUser());
		
			menu.findItem(R.id.action_login).setVisible(!realUser);						
			
			//Only registered user can see these buttons
			menu.findItem(R.id.action_logout).setVisible(realUser);	
			menu.findItem(R.id.measurements_list).setVisible(realUser);
			menu.findItem(R.id.measurements_graphs).setVisible(realUser);
			menu.findItem(R.id.referentiel).setVisible(realUser);
		}	
		menu.findItem(R.id.measurements_table).setVisible(false);
		return true;
	}
}